package com.wms.oms.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.wms.common.core.utils.DateUtils;
import com.wms.oms.domain.CheckOrder;
import com.wms.oms.domain.CheckOrderItem;
import com.wms.oms.domain.Inventory;
import com.wms.oms.domain.InventoryLog;
import com.wms.oms.domain.ProductSku;
import com.wms.oms.enums.ApprovalStatus;
import com.wms.oms.enums.InventoryType;
import com.wms.oms.mapper.CheckOrderItemMapper;
import com.wms.oms.mapper.CheckOrderMapper;
import com.wms.oms.service.ICheckOrderService;
import com.wms.oms.service.IInventoryLogService;
import com.wms.oms.service.IInventoryService;
import com.wms.oms.service.IProductSkuService;
import org.apache.commons.lang3.ObjectUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.Assert;

import java.util.List;

/**
 * @author zzm
 * @date 2023/8/18
 * @desc
 */
@Service
public class CheckOrderServiceImpl implements ICheckOrderService {

    @Autowired
    private CheckOrderMapper checkOrderMapper;

    @Autowired
    private CheckOrderItemMapper checkOrderItemMapper;

    @Autowired
    private IInventoryService inventoryService;

    @Autowired
    private IProductSkuService productSkuService;

    @Autowired
    private IInventoryLogService inventoryLogService;


    @Override
    public CheckOrder selectCheckOrderById(Long id) {
        return checkOrderMapper.selectById(id);
    }

    @Override
    public List<CheckOrder> selectCheckOrderList(CheckOrder CheckOrder) {
        return checkOrderMapper.selectList(new LambdaQueryWrapper<>());
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public int insertCheckOrder(CheckOrder checkOrder) {
        checkOrder.setSn("CK"+ DateUtils.getNowDate().getTime());
        checkOrder.setStatus(ApprovalStatus.WAIT_COMMIT.getValue());
        int result =checkOrderMapper.insert(checkOrder);
        List<CheckOrderItem> checkOrderItems = checkOrder.getCheckOrderItems();
        for (CheckOrderItem item : checkOrderItems) {
            item.setCheckOrderId(checkOrder.getId());
            Inventory inventory = inventoryService.selectInventoryByPro(item.getSkuId(), checkOrder.getWarehouseId());
            if (inventory.getQty().compareTo(item.getQty()) == -1) {
                item.setInventoryType(InventoryType.CHECK_IN.getValue());
            }
            else if(inventory.getQty().compareTo(item.getQty()) == 1){
                item.setInventoryType(InventoryType.CHECK_OUT.getValue());
            }
            item.setInvQty(inventory.getQty());
            checkOrderItemMapper.insert(item);
            inventory.setCheckFlag(Boolean.TRUE);
            // 新增的盘点单要锁住当前库存，等盘点结束才可以操作库存
            inventoryService.updateInventory(inventory);
        }
        return result;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public int updateCheckOrder(CheckOrder checkOrder) {
        CheckOrder oldCheckOrder = checkOrderMapper.selectById(checkOrder.getId());
        Assert.notNull(oldCheckOrder, "盘点单不存在!");
        int result = checkOrderMapper.updateById(checkOrder);
        List<CheckOrderItem> checkOrderItems = checkOrder.getCheckOrderItems();
        for (CheckOrderItem item : checkOrderItems) {
            if (ObjectUtils.isNotEmpty(item.getId())) {
                checkOrderItemMapper.updateById(item);
            }else {
                checkOrderItemMapper.insert(item);
            }
        }
        return result;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public int confirm(CheckOrder checkOrder) {
        CheckOrder model = checkOrderMapper.selectById(checkOrder.getId());
        List<CheckOrderItem> checkOrderItems = checkOrderItemMapper.selectList(
                new LambdaQueryWrapper<CheckOrderItem>().eq(CheckOrderItem::getCheckOrderId, checkOrder.getId()));
        for (CheckOrderItem item : checkOrderItems){
            Inventory inventory = inventoryService.selectInventoryByPro(item.getSkuId(), model.getWarehouseId());
            ProductSku productSku = productSkuService.selectById(item.getSkuId());
            if (ObjectUtils.isNotEmpty(inventory)) {
                inventory.setQty(item.getQty());
                // 盘点确认后释放库存操作
                inventory.setCheckFlag(Boolean.FALSE);
                inventoryService.updateInventory(inventory);
            }else {
                inventory = new Inventory();
                inventory.setProductId(productSku.getProductId());
                inventory.setSkuId(item.getSkuId());
                inventory.setWarehouseId(model.getWarehouseId());
                inventory.setQty(item.getQty());
                inventoryService.insertInventory(inventory);
            }

            // 库存操作日志
            InventoryLog inventoryLog = new InventoryLog();
            inventoryLog.setInventoryType(item.getInventoryType());
            inventoryLog.setQty(item.getQty().subtract(item.getInvQty()));
            inventoryLog.setPrice(productSku.getSalePrice());
            inventoryLog.setSn(model.getSn());
            inventoryLog.setWarehouseId(model.getWarehouseId());
            inventoryLog.setSkuId(productSku.getId());
            inventoryLogService.insertInventoryLog(inventoryLog);
        }
        // 已审批通过
        checkOrder.setStatus(ApprovalStatus.APPROVALED.getValue());
        checkOrderMapper.updateById(checkOrder);
        return 1;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public int deleteCheckOrderByIds(Long[] ids) {
        CheckOrder checkOrder = new CheckOrder();
        checkOrder.setDelFlag(Boolean.TRUE);
        checkOrderMapper.update(checkOrder, new LambdaQueryWrapper<CheckOrder>().in(CheckOrder::getId, ids));
        for (Long id : ids) {
            CheckOrder item = checkOrderMapper.selectById(id);
            List<CheckOrderItem> checkOrderItems = checkOrderItemMapper.selectList(
                    new LambdaQueryWrapper<CheckOrderItem>().eq(CheckOrderItem::getCheckOrderId, id));
            for (CheckOrderItem checkOrderItem : checkOrderItems) {
                Inventory inventory = inventoryService.selectInventoryByPro(checkOrderItem.getSkuId(), item.getWarehouseId());
                if (ObjectUtils.isNotEmpty(inventory)) {
                    // 删除后释放库存盘点操作
                    inventory.setCheckFlag(Boolean.FALSE);
                    inventoryService.updateInventory(inventory);
                }
            }

        }
        return 1;
    }
}
